#ifndef MT19937_H
#define MT19937_H

#include <stddef.h>

#ifdef __cplusplus
extern "C"{
#endif

typedef struct __mt19937_engine mt19937_engine;
typedef struct __mt19937_64_engine mt19937_64_engine;

mt19937_engine *create_mt19937(unsigned int seed);
mt19937_engine *create_mt19937_by_array(const unsigned int *keys, size_t count);
void destroy_mt19937(mt19937_engine *engine);
unsigned int mt19937_randuint32(mt19937_engine *engine);
int mt19937_randint31(mt19937_engine *engine);
double mt19937_randreal1(mt19937_engine *engine);
double mt19937_randreal2(mt19937_engine *engine);
double mt19937_randreal3(mt19937_engine *engine);
double mt19937_randres53(mt19937_engine *engine);

mt19937_64_engine *create_mt19937_64(unsigned long long seed);
mt19937_64_engine *create_mt19937_64_by_array(const unsigned long long *init_key,
             size_t key_length);
void destroy_mt19937_64(mt19937_64_engine *engine);
unsigned long long mt19937_64_randuint64(mt19937_64_engine *engine);
long long mt19937_64_randint63(mt19937_64_engine *engine);
double mt19937_64_randreal1(mt19937_64_engine *engine);
double mt19937_64_randreal2(mt19937_64_engine *engine);
double mt19937_64_randreal3(mt19937_64_engine *engine);

#ifdef __cplusplus
}
#endif


#endif // MT19937_H
